using System;

namespace Nice157Advices.Advices
{
    /// <summary>
    /// 59.不要在不恰当的场合下引发异常
    /// </summary>
    public static class _59
    {
        /**
         * /* NOTE
         * 1.理解 Try Parse 与 Tester Doer 两种模式
         * 2.抛出异常影响效率
         * 3.程序员，尤其是类库开发人员，要掌握的两条首页原则是：
         *      a.正常的业务不应使用异常来处理
         *      b.不要总是尝试去捕捉异常或引发异常，而应该允许异常向调用堆栈往上传播
         * 4.那么该在怎么样的情况下引发异常呢：
         *      a.第一类情况如果运行代码后会造成内存泄漏、资源不可用，或者应用程序状态不可恢复，则引发异常。[但是对在可控范围内的输入与输出不引发异常]
         *      b.第二类情况在捕获异常的时候，如果需要包装一些更有用的信息，则引发异常。这类异常的引发在UI层特别有用。系统引发的异常所带的信息往往更倾向于技术性的描述；而在UI层，面对异常的很可能是最终用户。如果需要将异常的信息呈现给最终用户，更好的做法是先包装异常，然后引发一个包含友好信息的新异常。
         *      c.第三类情况如果底层异常在高层操作的上下文中没有意义，则可以考虑捕获这些底层异常，并引发新的有意义的异常。(具体操作即在catch里throw一个便于理解的Exception)
         */

        public static void Go ()
        {
            var age = 101;

            // 这是一个正常的业务逻辑，不应该被处理为一个异常。
            // 而应该采用 Tester-Doer 来验证
            // if (age < 0)
            // {
            //     throw new ArgumentOutOfRangeException("Age不能为负数");
            // }
            string msg = string.Empty;
            if (CheckAge (age, ref msg))
            {
                System.Console.WriteLine ("checked true!");
            }
            else
            {
                System.Console.WriteLine ("checked false, and msg is: " + msg);
            }

        }

        private static bool CheckAge (int age, ref string msg)
        {
            if (age < 0)    // Tester
            {   // Doer
                msg = "Age不能为负数";
                return false;
            }
            else if (age > 100) // Tester
            {   // Doer
                msg = "Age不能大于100";
                return false;
            }
            return true;
        }
    }
}